package cn.drenal.capcap.service.impl;

import cn.drenal.capcap.entity.Activity;
import cn.drenal.capcap.entity.Category;
import cn.drenal.capcap.mapper.ActivityMapper;
import cn.drenal.capcap.mapper.ArtworkMapper;
import cn.drenal.capcap.mapper.CategoryMapper;
import cn.drenal.capcap.mapper.CommentMapper;
import cn.drenal.capcap.mapper.UserMapper;
import cn.drenal.capcap.service.StatisticsService;
import cn.drenal.capcap.entity.vo.CategoryDistributionVO;
import cn.drenal.capcap.entity.vo.DashboardStatisticsVO;
import cn.drenal.capcap.entity.vo.RecentActivityVO;
import cn.drenal.capcap.entity.vo.UserGrowthTrendVO;
import lombok.RequiredArgsConstructor;
import org.springframework.stereotype.Service;

import java.time.LocalDate;
import java.time.LocalDateTime;
import java.time.format.DateTimeFormatter;
import java.util.*;

/**
 * 统计服务实现类
 */
@Service
@RequiredArgsConstructor
public class StatisticsServiceImpl implements StatisticsService {

    private final UserMapper userMapper;

    private final ArtworkMapper artworkMapper;

    private final ActivityMapper activityMapper;

    private final CommentMapper commentMapper;

    private final CategoryMapper categoryMapper;

    /**
     * 获取仪表盘统计数据
     * 包括用户总数、作品总数、活动总数、评论总数及其环比增长率
     *
     * @return 统计数据VO
     */
    @Override
    public DashboardStatisticsVO getDashboardStatistics() {
        // 获取当前月份和上个月份
        LocalDate now = LocalDate.now();
        LocalDate firstDayOfCurrentMonth = now.withDayOfMonth(1);
        LocalDate firstDayOfLastMonth = firstDayOfCurrentMonth.minusMonths(1);
        
        // 格式化日期范围
        String currentMonthStart = firstDayOfCurrentMonth.format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
        String currentMonthEnd = now.format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
        String lastMonthStart = firstDayOfLastMonth.format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
        String lastMonthEnd = firstDayOfCurrentMonth.format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
        
        // 用户统计
        long currentUserCount = userMapper.selectCount(null);
        long lastMonthUserCount = userMapper.countUsersByDateRange(lastMonthStart, lastMonthEnd);
        double userGrowth = calculateGrowthRate(currentUserCount, lastMonthUserCount);
        
        // 作品统计
        long currentArtworkCount = artworkMapper.selectCount(null);
        long lastMonthArtworkCount = artworkMapper.countArtworksByDateRange(lastMonthStart, lastMonthEnd);
        double artworkGrowth = calculateGrowthRate(currentArtworkCount, lastMonthArtworkCount);
        
        // 活动统计
        long currentActivityCount = activityMapper.selectCount(null);
        long lastMonthActivityCount = activityMapper.countActivitiesByDateRange(lastMonthStart, lastMonthEnd);
        double activityGrowth = calculateGrowthRate(currentActivityCount, lastMonthActivityCount);
        
        // 评论统计
        long currentCommentCount = commentMapper.selectCount(null);
        long lastMonthCommentCount = commentMapper.countCommentsByDateRange(lastMonthStart, lastMonthEnd);
        double commentGrowth = calculateGrowthRate(currentCommentCount, lastMonthCommentCount);
        
        // 组装结果并返回VO对象
        return DashboardStatisticsVO.builder()
                .userCount((int) currentUserCount)
                .userGrowth(userGrowth)
                .artworkCount((int) currentArtworkCount)
                .artworkGrowth(artworkGrowth)
                .activityCount((int) currentActivityCount)
                .activityGrowth(activityGrowth)
                .commentCount((int) currentCommentCount)
                .commentGrowth(commentGrowth)
                .build();
    }

    /**
     * 获取用户增长趋势数据
     *
     * @param days 天数，默认30天
     * @return 用户增长趋势数据VO
     */
    @Override
    public UserGrowthTrendVO getUserGrowthTrend(Integer days) {
        if (days == null || days <= 0) {
            days = 30;
        }
        
        List<String> dates = new ArrayList<>();
        List<Integer> counts = new ArrayList<>();
        
        // 获取当前日期
        LocalDate now = LocalDate.now();
        DateTimeFormatter formatter = DateTimeFormatter.ofPattern("M/d");
        
        // 获取过去days天的用户增长数据
        for (int i = days - 1; i >= 0; i--) {
            LocalDate date = now.minusDays(i);
            String dateStr = date.format(DateTimeFormatter.ofPattern("yyyy-MM-dd"));
            dates.add(date.format(formatter));
            
            // 获取每天的新增用户数量
            counts.add(userMapper.countNewUsersByDate(dateStr));
        }
        
        // 返回VO对象
        return UserGrowthTrendVO.builder()
                .dates(dates)
                .counts(counts)
                .build();
    }

    /**
     * 获取作品分类分布数据
     *
     * @return 分类分布数据VO列表
     */
    @Override
    public List<CategoryDistributionVO> getCategoryDistribution() {
        // 获取所有分类
        List<Category> categories = categoryMapper.selectList(null);
        
        // 获取分类分布数据
        List<CategoryDistributionVO> result = new ArrayList<>();
        
        for (Category category : categories) {
            // 获取每个分类下的作品数量
            int value = artworkMapper.countArtworksByCategory(category.getId());
            
            // 创建并添加VO对象
            result.add(CategoryDistributionVO.builder()
                    .name(category.getName())
                    .value(value)
                    .build());
        }
        
        return result;
    }

    /**
     * 获取近期活动数据
     *
     * @param limit 获取数量
     * @return 活动数据VO列表
     */
    @Override
    public List<RecentActivityVO> getRecentActivities(Integer limit) {
        if (limit == null || limit <= 0) {
            limit = 5;
        }
        
        // 获取最近的活动数据
        List<Activity> activities = activityMapper.selectList(null);
        // 按开始时间倒序排序，取最近的limit条
        activities = activities.stream()
                .sorted(Comparator.comparing(Activity::getStartTime).reversed())
                .limit(limit)
                .toList();
        
        // 转换为VO对象列表
        List<RecentActivityVO> result = new ArrayList<>();
        Random random = new Random();
        
        for (Activity activity : activities) {
            // 根据当前时间判断活动状态
            LocalDateTime localDateTime = LocalDateTime.now();

            int status;
            if (localDateTime.isBefore(activity.getStartTime())) {
                status = 0; // 投稿期
            } else if (localDateTime.isAfter(activity.getEndTime())) {
                status = 2; // 投票期
            } else {
                status = 1; // 公示期
            }
            
            // 获取活动的作品数量和参与人数
            int artworkCount = activityMapper.countArtworksByActivity(activity.getId());
            int participantCount = activityMapper.countParticipantsByActivity(activity.getId());
            // 计算参与率（参与人数/总用户数 * 100）
            int totalUsers = Math.toIntExact(userMapper.selectCount(null));
            int participantRate = totalUsers > 0 ? (participantCount * 100 / totalUsers) : 0;
            
            // 创建并添加VO对象
            result.add(RecentActivityVO.builder()
                    .id(activity.getId())
                    .name(activity.getName())
                    .startTime(activity.getStartTime())
                    .endTime(activity.getEndTime())
                    .status(status)
                    .artworkCount(artworkCount)
                    .participantRate(participantRate)
                    .build());
        }
        
        return result;
    }
    
    /**
     * 计算环比增长率
     *
     * @param current 当前值
     * @param last 上期值
     * @return 增长率（百分比）
     */
    private double calculateGrowthRate(long current, long last) {
        if (last == 0) {
            return 100.0; // 避免除以零
        }
        return Math.round((current - last) * 100.0 / last * 10) / 10.0;
    }
}